package me.firstapp.service.weixin.product.impl;

import java.math.BigDecimal;
import java.math.RoundingMode;
import java.util.Date;
import java.util.List;
import java.util.Map;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import me.firstapp.common.exception.ServiceException;
import me.firstapp.common.exception.StatusHouse;
import me.firstapp.common.utils.DateUtils;
import me.firstapp.common.utils.MD5Utils;
import me.firstapp.common.utils.Page;
import me.firstapp.common.utils.StrUtils;
import me.firstapp.module.weixin.jinbi.JinBiAccount;
import me.firstapp.module.weixin.jinbi.JinBiAccountTrace;
import me.firstapp.module.weixin.member.Member;
import me.firstapp.module.weixin.member.PaymentRecord;
import me.firstapp.module.weixin.order.ProductOrder;
import me.firstapp.module.weixin.order.SoftOrder;
import me.firstapp.module.weixin.product.Product;
import me.firstapp.module.weixin.product.Supplier;
import me.firstapp.module.weixin.system.AccountRecordType;
import me.firstapp.module.weixin.system.ThisSystem;
import me.firstapp.module.weixin.weibi.WeiBiAccount;
import me.firstapp.module.weixin.weibi.WeiBiAccountTrace;
import me.firstapp.module.weixin.weibi.WeiBiAccountTrace.ChangeType;
import me.firstapp.repository.weixin.jinbi.JinBiAccountRepository;
import me.firstapp.repository.weixin.jinbi.JinBiAccountTraceRepository;
import me.firstapp.repository.weixin.member.MemberRepository;
import me.firstapp.repository.weixin.member.PaymentRecordRepository;
import me.firstapp.repository.weixin.order.ProductOrderRepository;
import me.firstapp.repository.weixin.product.ProductRepository;
import me.firstapp.repository.weixin.product.SupplierRepository;
import me.firstapp.repository.weixin.system.ThisSystemRepository;
import me.firstapp.repository.weixin.weibi.WeiBiAccountRepository;
import me.firstapp.repository.weixin.weibi.WeiBiAccountTraceRepository;
import me.firstapp.service.weixin.product.ProductOrderService;

@Service
public class ProductOrderServiceImpl implements ProductOrderService {

	private static Logger logger = LoggerFactory.getLogger(ProductOrderServiceImpl.class);

	@Autowired
	private ProductOrderRepository productOrderRepository;

	@Autowired
	private MemberRepository memberRepository;

	@Autowired
	private ProductRepository productRepository;

	@Autowired
	private ThisSystemRepository thisSystemRepository;

	@Autowired
	private PaymentRecordRepository paymentRecordRepository;

	@Autowired
	private WeiBiAccountRepository weiBiAccountRepository;

	@Autowired
	private WeiBiAccountTraceRepository weiBiAccountTraceRepository;

	@Autowired
	private JinBiAccountRepository jinBiAccountRepository;

	@Autowired
	private JinBiAccountTraceRepository jinBiAccountTraceRepository;

	@Autowired
	private SupplierRepository supplierRepository;

	@Override
	public ProductOrder executeCreateOrder(String openId, Long productId, int counts, String receiveName,
			String receiveMobile, String receiveAddress, String remark, String skuName) {
		Member member = memberRepository.findMemberByOpenId(openId);
		if (null == member) {
			throw new ServiceException(StatusHouse.STATUS_MEMBER_NOT_EXIST);
		}
		Product product = (Product) productRepository.getById(productId);
		if (null == product) {
			throw new ServiceException(StatusHouse.STATUS_PRODUCT_NOT_EXIST);
		}
		if (Product.STATUS_OFF == product.getStatus()) {
			throw new ServiceException(StatusHouse.STATUS_PRODUCT_OFF_ERROR);
		}
		if (product.getLimitUnit() != 0 && product.getLimitUnit() < counts) {
			throw new ServiceException("error", "数量超过限制!最大为" + product.getLimitUnit() + product.getUnit());
		}
		ProductOrder productOrder = new ProductOrder();
		member.setFlow(member.getFlow() + 1);
		memberRepository.update(member);
		String orderNoStart = ProductOrder.ORDER_NO_START + DateUtils.getNowStr("yyMMdd") + member.getId();
		String orderNoEnd = String.valueOf(member.getFlow());
		ThisSystem thisSystem = thisSystemRepository.findThisSystem();
		int lenth = thisSystem.getOrderNoLength() - orderNoStart.length() - orderNoEnd.length();
		StringBuffer sb = new StringBuffer("");
		for (int i = 0; i < lenth; i++) {
			sb.append(String.valueOf(StrUtils.getRandomInt()));
		}
		productOrder.setOrderNo(orderNoStart + sb.toString() + orderNoEnd);
		productOrder.setOpenId(openId);
		productOrder.setCardNo(member.getCardNo());
		productOrder.setChiefOpenId(member.getChiefOpenId());
		productOrder.setChiefCardNo(member.getChiefCardNo());
		productOrder.setSupplierId(product.getSupplierId());
		Supplier supplier = (Supplier) supplierRepository.getById(product.getSupplierId());
		if (null != supplier) {
			productOrder.setOutSysName(supplier.getSysName());
		}
		productOrder.setProductId(productId);
		productOrder.setName(product.getName());
		productOrder.setImgUrl(product.getImgUrl());
		productOrder.setDetailUrl(product.getDetailUrl());
		productOrder.setOutUrl(product.getOutUrl());
		productOrder.setCounts(counts);
		productOrder.setUnit(product.getUnit());
		BigDecimal freightAmount = product.getStartFreight();
		if (counts > 1) {
			freightAmount = product.getStartFreight().add(product.getUnitFreight().multiply(new BigDecimal(counts - 1)))
					.setScale(2, RoundingMode.HALF_UP);
		}
		productOrder.setFreightAmount(freightAmount);
		if (Member.VIP_LEVEL_FANS == member.getVipLevel()) {
			productOrder.setProductPrice(product.getFansPrice());
			productOrder.setProductAmount(
					product.getFansPrice().multiply(new BigDecimal(counts)).setScale(2, RoundingMode.HALF_UP));
		} else if (Member.VIP_LEVEL_BASE == member.getVipLevel()) {
			productOrder.setProductPrice(product.getBaseVipPrice());
			productOrder.setProductAmount(
					product.getBaseVipPrice().multiply(new BigDecimal(counts)).setScale(2, RoundingMode.HALF_UP));
		} else if (Member.VIP_LEVEL_HIGHT == member.getVipLevel()) {
			productOrder.setProductPrice(product.getHighVipPrice());
			productOrder.setProductAmount(
					product.getHighVipPrice().multiply(new BigDecimal(counts)).setScale(2, RoundingMode.HALF_UP));
		}
		productOrder.setTotalAmount(productOrder.getProductAmount().add(productOrder.getFreightAmount()));
		productOrder.setPayAmount(productOrder.getTotalAmount());
		productOrder.setGivePoint(productOrder.getProductAmount());
		productOrder.setChiefBaseVipJinBi(product.getChiefBaseVipJinBi().multiply(new BigDecimal(counts)));
		productOrder.setChiefHighVipJinBi(product.getChiefHighVipJinBi().multiply(new BigDecimal(counts)));
		productOrder.setChiefBaseVipPoint(product.getChiefBaseVipPoint().multiply(new BigDecimal(counts)));
		productOrder.setChiefHighVipPoint(product.getChiefHighVipPoint().multiply(new BigDecimal(counts)));
		productOrder.setFansBuyGiveOtherJb(product.getFansBuyGiveOtherJb().multiply(new BigDecimal(counts)));
		productOrder.setBaseVipBuyGiveOtherJb(product.getBaseVipBuyGiveOtherJb().multiply(new BigDecimal(counts)));
		productOrder.setHighVipBuyGiveOtherJb(product.getHighVipBuyGiveOtherJb().multiply(new BigDecimal(counts)));
		productOrder.setChiefJinBi(BigDecimal.ZERO);
		productOrder.setChiefPoint(BigDecimal.ZERO);
		productOrder.setChiefChiefJinBi(BigDecimal.ZERO);
		productOrder.setStatus(ProductOrder.STATUS_NOT_PAY);
		productOrder.setCreateTime(new Date());
		productOrder.setSettleFlag(ProductOrder.SETTLE_FLAG_NOT);
		productOrder.setReceiveName(receiveName);
		productOrder.setReceiveMobile(receiveMobile);
		productOrder.setReceiveAddress(receiveAddress);
		productOrder.setRemark(remark);
		productOrder.setSkuName(skuName);
		productOrderRepository.save(productOrder);
		return productOrder;
	}

	@Override
	public ProductOrder findByOrderNo(String openId, String orderNo) {
		return productOrderRepository.findByOrderNo(openId, orderNo);
	}

	@Override
	public void executeConfirmOrder(ProductOrder productOrder) {
		if (null == productOrder) {
			return;
		}
		if (ProductOrder.STATUS_NOT_PAY != productOrder.getStatus()) {
			return;
		}
		productOrder.setStatus(ProductOrder.STATUS_PAYED);
		productOrder.setAccountDate(new Date());
		productOrderRepository.update(productOrder);
	}

	@Override
	public void executeSavePaymentRecord(ProductOrder productOrder, String thirdPayNo, Integer status, String errorCode,
			String errorDesc) {
		if (productOrder == null) {
			return;
		}
		if (ProductOrder.STATUS_PAYED != productOrder.getStatus()) {
			return;
		}
		PaymentRecord paymentRecord = new PaymentRecord();
		paymentRecord.setOrderNo(productOrder.getOrderNo());
		paymentRecord.setOpenId(productOrder.getOpenId());
		paymentRecord.setCardNo(productOrder.getCardNo());
		paymentRecord.setThirdPayNo(thirdPayNo);
		paymentRecord.setPayAmount(productOrder.getPayAmount());
		paymentRecord.setStatus(status);
		paymentRecord.setPayTime(new Date());
		paymentRecord.setErrorCode(errorCode);
		paymentRecord.setErrorDesc(errorDesc);
		paymentRecordRepository.save(paymentRecord);
	}

	@Override
	public ProductOrder findByOrderNo(String orderNo) {
		return productOrderRepository.findByOrderNo(orderNo);
	}

	@Override
	public List<ProductOrder> findOrders(Integer status) {
		return productOrderRepository.findOrders(status);
	}

	@Override
	public List<ProductOrder> findOrders(Integer status, Integer settleFlag) {
		return productOrderRepository.findOrders(status, settleFlag);
	}

	@Override
	public ProductOrder executeCancelOrder(ProductOrder productOrder) {
		productOrder.setStatus(ProductOrder.STATUS_CANCEL);
		productOrder.setCancelTime(new Date());
		productOrderRepository.update(productOrder);
		return productOrder;
	}

	@Override
	public ProductOrder executeSettle(ProductOrder productOrder) {
		if (ProductOrder.SETTLE_FLAG_YES == productOrder.getSettleFlag()) {
			return productOrder;
		}
		if (ProductOrder.STATUS_COMPLETE != productOrder.getStatus()) {
			return productOrder;
		}
		Member member = memberRepository.findMemberByOpenId(productOrder.getOpenId());

		// ==================模块二：上级结算 start=======================
		Member chiefMember = memberRepository.findMemberByOpenId(productOrder.getChiefOpenId());
		if (null == chiefMember) {
			productOrder.setChiefJinBi(BigDecimal.ZERO);
			productOrder.setChiefChiefJinBi(BigDecimal.ZERO);
			productOrder.setChiefPoint(BigDecimal.ZERO);
			// 更新订单结算标志
			productOrder.setSettleFlag(ProductOrder.SETTLE_FLAG_YES);
			productOrder.setSettleTime(new Date());
			productOrderRepository.update(productOrder);
			logger.info("商品订单【" + productOrder.getOrderNo() + "】已结算完成。");
			return productOrder;
		}
		if (chiefMember.getVipLevel() == Member.VIP_LEVEL_FANS) {
			productOrder.setChiefJinBi(BigDecimal.ZERO);
			productOrder.setChiefPoint(BigDecimal.ZERO);
			logger.info("用户【" + member.getCardNo() + "】的上级【" + chiefMember.getCardNo() + "】的等级为粉丝，无需结算");
		} else if (Member.STATUS_NO_USE == chiefMember.getStatus()
				|| Member.FOLLOW_STATUS_NO == chiefMember.getFollowStatus()) {
			productOrder.setChiefJinBi(BigDecimal.ZERO);
			productOrder.setChiefPoint(BigDecimal.ZERO);
			logger.info("用户【" + member.getCardNo() + "】的上级【" + chiefMember.getCardNo() + "】的被禁用或取消关注，无需结算");
		} else {
			// ==========上级积分结算 start=============
			WeiBiAccount chiefWeiBiAccount = weiBiAccountRepository
					.findWeiBiAccountByCardNoAndOpenId(chiefMember.getCardNo(), chiefMember.getOpenId());
			if (!MD5Utils.verify(chiefWeiBiAccount.getBalance().doubleValue() * 10000 + "",
					chiefWeiBiAccount.getEncryption())) {
				productOrder.setChiefPoint(BigDecimal.ZERO);
				logger.info("用户【" + member.getCardNo() + "】的上级【" + chiefMember.getCardNo() + "】的积分账户金额异常!");
			} else {
				BigDecimal chiefMemberWeiBiChangeValue = BigDecimal.ZERO;
				if (chiefMember.getVipLevel() == Member.VIP_LEVEL_BASE) {
					chiefMemberWeiBiChangeValue = productOrder.getChiefBaseVipPoint();
				} else if (chiefMember.getVipLevel() == Member.VIP_LEVEL_HIGHT) {
					chiefMemberWeiBiChangeValue = productOrder.getChiefHighVipPoint();
				}
				if (chiefMemberWeiBiChangeValue.doubleValue() <= 0.00009999) {
					productOrder.setChiefPoint(BigDecimal.ZERO);
					logger.info("订单【" + productOrder.getOrderNo() + "】待赠送购买者上级的积分为0!");
				} else {
					WeiBiAccountTrace chiefMemberWeiBiAccountTrace = new WeiBiAccountTrace();
					chiefMemberWeiBiAccountTrace.setWeiBiAccountId(chiefWeiBiAccount.getId());
					chiefMemberWeiBiAccountTrace.setChangeType(ChangeType.FANS_CONSUME_ADD);
					chiefMemberWeiBiAccountTrace.setBeforeValue(chiefWeiBiAccount.getBalance());
					chiefMemberWeiBiAccountTrace.setChangeValue(chiefMemberWeiBiChangeValue);
					BigDecimal chiefMemberWeiBiAfterValue = chiefWeiBiAccount.getBalance()
							.add(chiefMemberWeiBiChangeValue).setScale(4, RoundingMode.HALF_UP);
					chiefMemberWeiBiAccountTrace.setAfterValue(chiefMemberWeiBiAfterValue);
					chiefMemberWeiBiAccountTrace.setChangeTime(new Date());
					chiefMemberWeiBiAccountTrace
							.setChangeDate(Integer.valueOf(DateUtils.getDateStr(new Date(), "yyyyMMdd")));
					weiBiAccountTraceRepository.save(chiefMemberWeiBiAccountTrace);

					chiefWeiBiAccount.setBalance(chiefMemberWeiBiAfterValue);
					chiefWeiBiAccount
							.setEncryption(MD5Utils.generate(chiefMemberWeiBiAfterValue.doubleValue() * 10000 + ""));
					chiefWeiBiAccount.setUpdateTime(new Date());
					weiBiAccountRepository.update(chiefWeiBiAccount);
					productOrder.setChiefPoint(chiefMemberWeiBiChangeValue);
				}

			}
			// ==========上级积分结算 end=============

			// ==========上级贝币结算 start=============
			JinBiAccount chiefMemberJinBiAccount = jinBiAccountRepository
					.findJinBiAccountByCardNoAndOpenId(chiefMember.getCardNo(), chiefMember.getOpenId());
			if (!MD5Utils.verify(chiefMemberJinBiAccount.getBalance().doubleValue() * 10000 + "",
					chiefMemberJinBiAccount.getEncryption())) {
				productOrder.setChiefJinBi(BigDecimal.ZERO);
				logger.info("用户【" + member.getCardNo() + "】的上级【" + chiefMember.getCardNo() + "】的贝币账户金额异常!");
			} else {
				BigDecimal chiefMemberJinBiChangeValue = BigDecimal.ZERO;
				if (chiefMember.getVipLevel() == Member.VIP_LEVEL_BASE) {
					chiefMemberJinBiChangeValue = productOrder.getChiefBaseVipJinBi();
				} else if (chiefMember.getVipLevel() == Member.VIP_LEVEL_HIGHT) {
					chiefMemberJinBiChangeValue = productOrder.getChiefHighVipJinBi();
				}
				if (chiefMemberJinBiChangeValue.doubleValue() <= 0.00009999) {
					productOrder.setChiefJinBi(BigDecimal.ZERO);
					logger.info("订单【" + productOrder.getOrderNo() + "】待赠送购买者上级的贝币为0!");
				} else {
					JinBiAccountTrace chiefMemberinBiAccountTrace = new JinBiAccountTrace();
					chiefMemberinBiAccountTrace.setJinBiAccountId(chiefMemberJinBiAccount.getId());
					chiefMemberinBiAccountTrace.setChangeType(
							me.firstapp.module.weixin.jinbi.JinBiAccountTrace.ChangeType.FANS_CONSUME_ADD);
					chiefMemberinBiAccountTrace.setBeforeValue(chiefMemberJinBiAccount.getBalance());
					chiefMemberinBiAccountTrace.setChangeValue(chiefMemberJinBiChangeValue);
					BigDecimal chiefMemberJinBiAfterValue = chiefMemberJinBiAccount.getBalance()
							.add(chiefMemberJinBiChangeValue).setScale(4, RoundingMode.HALF_UP);
					chiefMemberinBiAccountTrace.setAfterValue(chiefMemberJinBiAfterValue);
					chiefMemberinBiAccountTrace.setChangeTime(new Date());
					chiefMemberinBiAccountTrace
							.setChangeDate(Integer.valueOf(DateUtils.getDateStr(new Date(), "yyyyMMdd")));
					jinBiAccountTraceRepository.save(chiefMemberinBiAccountTrace);

					chiefMemberJinBiAccount.setBalance(chiefMemberJinBiAfterValue);
					chiefMemberJinBiAccount
							.setEncryption(MD5Utils.generate(chiefMemberJinBiAfterValue.doubleValue() * 10000 + ""));
					chiefMemberJinBiAccount.setUpdateTime(new Date());
					jinBiAccountRepository.update(chiefMemberJinBiAccount);
					productOrder.setChiefJinBi(chiefMemberJinBiChangeValue);
				}
				// ---额外贝币赠送
				BigDecimal otherGiveJinBi = BigDecimal.ZERO;
				if (Member.VIP_LEVEL_FANS == member.getVipLevel()
						&& Member.VIP_LEVEL_HIGHT == chiefMember.getVipLevel()) {
					otherGiveJinBi = productOrder.getFansBuyGiveOtherJb();
				} else if (Member.VIP_LEVEL_BASE == member.getVipLevel()
						&& Member.VIP_LEVEL_HIGHT == chiefMember.getVipLevel()) {
					otherGiveJinBi = productOrder.getBaseVipBuyGiveOtherJb();
				} else if (Member.VIP_LEVEL_HIGHT == member.getVipLevel()
						&& Member.VIP_LEVEL_HIGHT == chiefMember.getVipLevel()) {
					otherGiveJinBi = productOrder.getHighVipBuyGiveOtherJb();
				}
				if (otherGiveJinBi.doubleValue() <= 0.000099999) {
					logger.info("订单【" + productOrder.getOrderNo() + "】待赠送购买者上级代理的额外贝币为0!");
				} else {
					JinBiAccountTrace chiefMemberinBiAccountTrace = new JinBiAccountTrace();
					chiefMemberinBiAccountTrace.setJinBiAccountId(chiefMemberJinBiAccount.getId());
					chiefMemberinBiAccountTrace.setChangeType(
							me.firstapp.module.weixin.jinbi.JinBiAccountTrace.ChangeType.XIAJI_OTHER_ADD);
					chiefMemberinBiAccountTrace.setBeforeValue(chiefMemberJinBiAccount.getBalance());
					chiefMemberinBiAccountTrace.setChangeValue(otherGiveJinBi);
					BigDecimal chiefMemberJinBiAfterValue = chiefMemberJinBiAccount.getBalance().add(otherGiveJinBi)
							.setScale(4, RoundingMode.HALF_UP);
					chiefMemberinBiAccountTrace.setAfterValue(chiefMemberJinBiAfterValue);
					chiefMemberinBiAccountTrace.setChangeTime(new Date());
					chiefMemberinBiAccountTrace
							.setChangeDate(Integer.valueOf(DateUtils.getDateStr(new Date(), "yyyyMMdd")));
					jinBiAccountTraceRepository.save(chiefMemberinBiAccountTrace);

					chiefMemberJinBiAccount.setBalance(chiefMemberJinBiAfterValue);
					chiefMemberJinBiAccount
							.setEncryption(MD5Utils.generate(chiefMemberJinBiAfterValue.doubleValue() * 10000 + ""));
					chiefMemberJinBiAccount.setUpdateTime(new Date());
					jinBiAccountRepository.update(chiefMemberJinBiAccount);
					productOrder.setChiefJinBi(productOrder.getChiefJinBi().add(otherGiveJinBi));
				}
			}
			// ==========上级贝币结算 end===============
		}
		// ==================上级结算 end=======================

		// //
		// ===========模块三：上级的上级如果是代理级别，则可吃下级代理的返利[返利计算：支付金额x0.2%x50%]==============
		Member chiefChiefMember = memberRepository.findMemberByOpenId(chiefMember.getChiefOpenId());
		if (null == chiefChiefMember) {
			productOrder.setChiefChiefJinBi(BigDecimal.ZERO);
			// 更新订单结算标志
			productOrder.setSettleFlag(ProductOrder.SETTLE_FLAG_YES);
			productOrder.setSettleTime(new Date());
			productOrderRepository.update(productOrder);
			logger.info("商品订单【" + productOrder.getOrderNo() + "】已结算完成。");
			return productOrder;
		}

		if (Member.STATUS_NO_USE == chiefChiefMember.getStatus()
				|| Member.FOLLOW_STATUS_NO == chiefChiefMember.getFollowStatus()
				|| Member.STATUS_NO_USE == chiefMember.getStatus()
				|| Member.FOLLOW_STATUS_NO == chiefMember.getFollowStatus()) {
			productOrder.setChiefChiefJinBi(BigDecimal.ZERO);
			logger.info("用户【" + member.getCardNo() + "】的上级【" + chiefMember.getCardNo() + "】或其上级【"
					+ chiefChiefMember.getCardNo() + "】被禁用或取消关注，无需结算");
		} else if ((Member.VIP_LEVEL_HIGHT == chiefChiefMember.getVipLevel())
				&& (Member.VIP_LEVEL_HIGHT == chiefMember.getVipLevel())) {
			BigDecimal changeJinBiValue = productOrder.getProductAmount().multiply(new BigDecimal(0.002))
					.multiply(new BigDecimal(0.5)).setScale(4, RoundingMode.HALF_UP);
			if (changeJinBiValue.doubleValue() > 0.000099999) {
				JinBiAccount jinBiAccount = jinBiAccountRepository
						.findJinBiAccountByCardNoAndOpenId(chiefChiefMember.getCardNo(), chiefChiefMember.getOpenId());
				if (MD5Utils.verify(jinBiAccount.getBalance().doubleValue() * 10000 + "",
						jinBiAccount.getEncryption())) {
					JinBiAccountTrace jinBiAccountTrace = new JinBiAccountTrace();
					jinBiAccountTrace.setJinBiAccountId(jinBiAccount.getId());
					jinBiAccountTrace.setChangeType(
							me.firstapp.module.weixin.jinbi.JinBiAccountTrace.ChangeType.JINBI_ADD_DAILI);
					jinBiAccountTrace.setBeforeValue(jinBiAccount.getBalance());
					jinBiAccountTrace.setChangeValue(changeJinBiValue);
					BigDecimal afterValue = jinBiAccount.getBalance().add(changeJinBiValue).setScale(4,
							RoundingMode.HALF_UP);
					jinBiAccountTrace.setAfterValue(afterValue);
					jinBiAccountTrace.setChangeTime(new Date());
					jinBiAccountTrace.setChangeDate(Integer.valueOf(DateUtils.getDateStr(new Date(), "yyyyMMdd")));
					jinBiAccountTraceRepository.save(jinBiAccountTrace);

					jinBiAccount.setBalance(afterValue);
					jinBiAccount.setEncryption(MD5Utils.generate(afterValue.doubleValue() * 10000 + ""));
					jinBiAccount.setUpdateTime(new Date());
					jinBiAccountRepository.update(jinBiAccount);
					productOrder.setChiefChiefJinBi(changeJinBiValue);
				} else {
					productOrder.setChiefChiefJinBi(BigDecimal.ZERO);
					logger.info("用户【" + member.getCardNo() + "】的上级【" + chiefMember.getCardNo() + "】的上级【"
							+ chiefChiefMember.getCardNo() + "】的贝币账户金额异常!");
				}
			} else {
				productOrder.setChiefChiefJinBi(BigDecimal.ZERO);
			}
		} else {
			productOrder.setChiefChiefJinBi(BigDecimal.ZERO);
		}
		// // ===========模块三end==============

		// 更新订单结算标志
		productOrder.setSettleFlag(ProductOrder.SETTLE_FLAG_YES);
		productOrder.setSettleTime(new Date());
		productOrderRepository.update(productOrder);
		logger.info("商品订单【" + productOrder.getOrderNo() + "】已结算完成。");
		return productOrder;
	}

	@Override
	public List<ProductOrder> findOrdersPage(int pageIndex, int pageSize, String openId, Integer status) {
		return productOrderRepository.findOrdersPage(pageIndex, pageSize, openId, status);
	}

	@Override
	public Page<ProductOrder> findProductOrderPage(Integer pageNo, Integer pageSize, Map<String, Object> searchParams,
			String sortParam, String sortType, Date startTime, Date endTime) {
		return productOrderRepository.findProductOrderPage(pageNo, pageSize, searchParams, sortParam, sortType,
				startTime, endTime);
	}

	@Override
	public ProductOrder executeUpdate(ProductOrder productOrder) {
		productOrderRepository.update(productOrder);
		return productOrder;
	}

	@Override
	public ProductOrder executeBeiBiPay(ProductOrder productOrder, Member member) {
		if (null == productOrder) {
			throw new ServiceException(StatusHouse.STATUS_ORDER_NOT_EXIST);
		}
		if (null == member) {
			throw new ServiceException(StatusHouse.STATUS_MEMBER_NOT_EXIST);
		}
		if (!productOrder.getOpenId().equals(member.getOpenId())
				&& !productOrder.getCardNo().equals(member.getCardNo())) {
			logger.error("订单【" + productOrder.getOrderNo() + "】所属用户与付款用户不一致");
			throw new ServiceException("error", "订单状态异常");
		}
		if (SoftOrder.STATUS_NOT_PAY != productOrder.getStatus()) {
			logger.error("订单【" + productOrder.getOrderNo() + "】不是未支付状态");
			throw new ServiceException("error", "订单状态异常");
		}

		// 扣减账户
		JinBiAccount jinBiAccount = jinBiAccountRepository.findJinBiAccountByCardNoAndOpenId(productOrder.getCardNo(),
				productOrder.getOpenId());
		if (!MD5Utils.verify(jinBiAccount.getBalance().doubleValue() * 10000 + "", jinBiAccount.getEncryption())) {
			logger.error("用户【" + member.getCardNo() + "】贝币账户金额异常!");
			throw new ServiceException("error", "贝币账户异常!");
		}
		if (jinBiAccount.getBalance().subtract(productOrder.getPayAmount()).doubleValue() < 0.0000999) {
			throw new ServiceException("error", "贝币账户余额不足!");
		}
		JinBiAccountTrace jinBiAccountTrace = new JinBiAccountTrace();
		jinBiAccountTrace.setJinBiAccountId(jinBiAccount.getId());
		jinBiAccountTrace.setChangeType(me.firstapp.module.weixin.jinbi.JinBiAccountTrace.ChangeType.CONSUME_SUB);
		jinBiAccountTrace.setBeforeValue(jinBiAccount.getBalance());
		jinBiAccountTrace.setChangeValue(productOrder.getPayAmount());
		BigDecimal afterValue = BigDecimal.ZERO;
		afterValue = jinBiAccount.getBalance().subtract(productOrder.getPayAmount()).setScale(4, RoundingMode.HALF_UP);
		jinBiAccountTrace.setAfterValue(afterValue);
		jinBiAccountTrace.setChangeDate(Integer.valueOf(DateUtils.getDateStr(new Date(), "yyyyMMdd")));
		jinBiAccountTrace.setChangeTime(new Date());
		jinBiAccountTraceRepository.save(jinBiAccountTrace);

		jinBiAccount.setBalance(afterValue);
		jinBiAccount.setEncryption(MD5Utils.generate(afterValue.doubleValue() * 10000 + ""));
		jinBiAccount.setUpdateTime(new Date());
		jinBiAccountRepository.update(jinBiAccount);

		// 更新商品销售数量
		Product product = (Product) productRepository.getById(productOrder.getProductId());
		product.setSaleCounts(product.getSaleCounts() + productOrder.getCounts());
		productRepository.update(product);

		// 更新订单
		productOrder.setStatus(SoftOrder.STATUS_PAYED);
		productOrder.setAccountDate(new Date());
		productOrder.setPayTime(new Date());
		productOrderRepository.update(productOrder);
		return productOrder;
	}

	@Override
	public ProductOrder executeReturn(ProductOrder productOrder) {
		if (ProductOrder.STATUS_PAYED != productOrder.getStatus()
				&& ProductOrder.STATUS_COMPLETE != productOrder.getStatus()) {
			throw new ServiceException("error", "订单不是已支付或已完成状态");
		}
		JinBiAccount jinBiAccount = jinBiAccountRepository.findJinBiAccountByCardNoAndOpenId(productOrder.getCardNo(),
				productOrder.getOpenId());
		if (!MD5Utils.verify(jinBiAccount.getBalance().doubleValue() * 10000 + "", jinBiAccount.getEncryption())) {
			logger.error("用户【" + productOrder.getCardNo() + "】贝币账户金额异常!");
			throw new ServiceException("error", "贝币账户异常!");
		}
		changeJinBi(jinBiAccount, productOrder.getPayAmount(),
				me.firstapp.module.weixin.jinbi.JinBiAccountTrace.ChangeType.RETURN_ADD);

		if (ProductOrder.STATUS_PAYED == productOrder.getStatus()) {
			productOrder.setStatus(ProductOrder.STATUS_RETURN);
		} else if (ProductOrder.STATUS_COMPLETE == productOrder.getStatus()
				&& ProductOrder.SETTLE_FLAG_YES == productOrder.getSettleFlag()) {
			if (productOrder.getGivePoint().doubleValue() > 0.00009999) {
				WeiBiAccount memberWeiBiAccount = weiBiAccountRepository
						.findWeiBiAccountByCardNoAndOpenId(productOrder.getCardNo(), productOrder.getOpenId());
				if (!MD5Utils.verify(memberWeiBiAccount.getBalance().doubleValue() * 10000 + "",
						memberWeiBiAccount.getEncryption())) {
					logger.info("用户【" + memberWeiBiAccount.getCardNo() + "】积分账户金额异常!");
					throw new ServiceException("error", "用户【" + productOrder.getCardNo() + "】积分账户金额异常!");
				}
				changeWeiBi(memberWeiBiAccount, ChangeType.RETURN_SUB, productOrder.getGivePoint());
			}

			Member chiefMember = memberRepository.findMemberByOpenId(productOrder.getChiefOpenId());
			if (null != chiefMember) {
				if (null != productOrder.getChiefPoint() && productOrder.getChiefPoint().doubleValue() > 0.00009999) {
					WeiBiAccount chiefMemberWeiBiAccount = weiBiAccountRepository
							.findWeiBiAccountByCardNoAndOpenId(chiefMember.getCardNo(), chiefMember.getOpenId());
					if (!MD5Utils.verify(chiefMemberWeiBiAccount.getBalance().doubleValue() * 10000 + "",
							chiefMemberWeiBiAccount.getEncryption())) {
						logger.info("用户【" + chiefMemberWeiBiAccount.getCardNo() + "】积分账户金额异常!");
						throw new ServiceException("error", "用户【" + chiefMemberWeiBiAccount.getCardNo() + "】积分账户金额异常!");
					}
					changeWeiBi(chiefMemberWeiBiAccount, ChangeType.J_RETURN_SUB, productOrder.getChiefPoint());
				}

				if (null != productOrder.getChiefJinBi() && productOrder.getChiefJinBi().doubleValue() > 0.00009999) {
					JinBiAccount chiefMemberJinBiAccount = jinBiAccountRepository
							.findJinBiAccountByCardNoAndOpenId(chiefMember.getCardNo(), chiefMember.getOpenId());
					if (!MD5Utils.verify(chiefMemberJinBiAccount.getBalance().doubleValue() * 10000 + "",
							chiefMemberJinBiAccount.getEncryption())) {
						logger.error("用户【" + chiefMemberJinBiAccount.getCardNo() + "】贝币账户金额异常!");
						throw new ServiceException("error", "贝币账户异常!");
					}
					changeJinBi(chiefMemberJinBiAccount, productOrder.getChiefJinBi(),
							me.firstapp.module.weixin.jinbi.JinBiAccountTrace.ChangeType.J_RETURN_SUB);
				}

				Member chiefChiefMember = memberRepository.findMemberByOpenId(chiefMember.getChiefOpenId());
				if (null != chiefChiefMember) {
					if (null != productOrder.getChiefChiefJinBi()
							&& productOrder.getChiefChiefJinBi().doubleValue() > 0.00009999) {
						JinBiAccount chiefChiefMemberJinBiAccount = jinBiAccountRepository
								.findJinBiAccountByCardNoAndOpenId(chiefChiefMember.getCardNo(),
										chiefChiefMember.getOpenId());
						if (!MD5Utils.verify(chiefChiefMemberJinBiAccount.getBalance().doubleValue() * 10000 + "",
								chiefChiefMemberJinBiAccount.getEncryption())) {
							logger.error("用户【" + chiefChiefMemberJinBiAccount.getCardNo() + "】贝币账户金额异常!");
							throw new ServiceException("error", "贝币账户异常!");
						}
						changeJinBi(chiefChiefMemberJinBiAccount, productOrder.getChiefChiefJinBi(),
								me.firstapp.module.weixin.jinbi.JinBiAccountTrace.ChangeType.J_RETURN_SUB);
					}
				}
			}
		}
		productOrder.setStatus(ProductOrder.STATUS_RETURN);
		productOrder.setReturnTime(new Date());
		productOrderRepository.update(productOrder);

		// 更新商品销售数量
		Product product = (Product) productRepository.getById(productOrder.getProductId());
		long counts = product.getSaleCounts() - productOrder.getCounts();
		if (counts < 0) {
			counts = 0;
		}
		product.setSaleCounts(counts);
		productRepository.update(product);

		return productOrder;
	}

	private void changeJinBi(JinBiAccount jinBiAccount, BigDecimal changeValue,
			me.firstapp.module.weixin.jinbi.JinBiAccountTrace.ChangeType changeType) {
		JinBiAccountTrace jinBiAccountTrace = new JinBiAccountTrace();
		jinBiAccountTrace.setJinBiAccountId(jinBiAccount.getId());
		jinBiAccountTrace.setChangeType(changeType);
		jinBiAccountTrace.setBeforeValue(jinBiAccount.getBalance());
		jinBiAccountTrace.setChangeValue(changeValue);

		BigDecimal afterValue = BigDecimal.ZERO;
		if (changeType.getAccountRecordType() == AccountRecordType.ADD) {
			afterValue = jinBiAccount.getBalance().add(changeValue).setScale(4, RoundingMode.HALF_UP);
		} else if (changeType.getAccountRecordType() == AccountRecordType.SUB) {
			afterValue = jinBiAccount.getBalance().subtract(changeValue).setScale(4, RoundingMode.HALF_UP);
		}

		jinBiAccountTrace.setAfterValue(afterValue);
		jinBiAccountTrace.setChangeDate(Integer.valueOf(DateUtils.getDateStr(new Date(), "yyyyMMdd")));
		jinBiAccountTrace.setChangeTime(new Date());
		jinBiAccountTraceRepository.save(jinBiAccountTrace);

		jinBiAccount.setBalance(afterValue);
		jinBiAccount.setEncryption(MD5Utils.generate(afterValue.doubleValue() * 10000 + ""));
		jinBiAccount.setUpdateTime(new Date());
		jinBiAccountRepository.update(jinBiAccount);
	}

	private void changeWeiBi(WeiBiAccount weiBiAccount, ChangeType changeType, BigDecimal changeValue) {
		WeiBiAccountTrace memberWeiBiAccountTrace = new WeiBiAccountTrace();
		memberWeiBiAccountTrace.setWeiBiAccountId(weiBiAccount.getId());
		memberWeiBiAccountTrace.setChangeType(changeType);
		memberWeiBiAccountTrace.setBeforeValue(weiBiAccount.getBalance());
		memberWeiBiAccountTrace.setChangeValue(changeValue);

		BigDecimal memberWeiBiAfterValue = BigDecimal.ZERO;
		if (changeType.getAccountRecordType() == AccountRecordType.ADD) {
			memberWeiBiAfterValue = weiBiAccount.getBalance().add(changeValue).setScale(4, RoundingMode.HALF_UP);
		} else if (changeType.getAccountRecordType() == AccountRecordType.SUB) {
			memberWeiBiAfterValue = weiBiAccount.getBalance().subtract(changeValue).setScale(4, RoundingMode.HALF_UP);
		}

		memberWeiBiAccountTrace.setAfterValue(memberWeiBiAfterValue);
		memberWeiBiAccountTrace.setChangeTime(new Date());
		memberWeiBiAccountTrace.setChangeDate(Integer.valueOf(DateUtils.getDateStr(new Date(), "yyyyMMdd")));
		weiBiAccountTraceRepository.save(memberWeiBiAccountTrace);

		weiBiAccount.setBalance(memberWeiBiAfterValue);
		weiBiAccount.setEncryption(MD5Utils.generate(memberWeiBiAfterValue.doubleValue() * 10000 + ""));
		weiBiAccount.setUpdateTime(new Date());
		weiBiAccountRepository.update(weiBiAccount);
	}

	@Override
	public void executeGivePoint(ProductOrder productOrder) {
		if (productOrder.getStatus() != ProductOrder.STATUS_PAYED) {
			return;
		}
		// ==========模块一：购物者积分结算 start=============
		WeiBiAccount memberWeiBiAccount = weiBiAccountRepository
				.findWeiBiAccountByCardNoAndOpenId(productOrder.getCardNo(), productOrder.getOpenId());
		if (!MD5Utils.verify(memberWeiBiAccount.getBalance().doubleValue() * 10000 + "",
				memberWeiBiAccount.getEncryption())) {
			logger.info("用户【" + productOrder.getCardNo() + "】积分账户金额异常!");
		} else {
			if (productOrder.getGivePoint().doubleValue() <= 0.00009999) {
				logger.info("订单【" + productOrder.getOrderNo() + "】待赠送购买者积分为0!");
			} else {
				WeiBiAccountTrace memberWeiBiAccountTrace = new WeiBiAccountTrace();
				memberWeiBiAccountTrace.setWeiBiAccountId(memberWeiBiAccount.getId());
				memberWeiBiAccountTrace.setChangeType(ChangeType.SELF_CONSUME_ADD);
				memberWeiBiAccountTrace.setBeforeValue(memberWeiBiAccount.getBalance());
				memberWeiBiAccountTrace.setChangeValue(productOrder.getGivePoint());
				BigDecimal memberWeiBiAfterValue = memberWeiBiAccount.getBalance().add(productOrder.getGivePoint())
						.setScale(4, RoundingMode.HALF_UP);
				memberWeiBiAccountTrace.setAfterValue(memberWeiBiAfterValue);
				memberWeiBiAccountTrace.setChangeTime(new Date());
				memberWeiBiAccountTrace.setChangeDate(Integer.valueOf(DateUtils.getDateStr(new Date(), "yyyyMMdd")));
				weiBiAccountTraceRepository.save(memberWeiBiAccountTrace);

				memberWeiBiAccount.setBalance(memberWeiBiAfterValue);
				memberWeiBiAccount.setEncryption(MD5Utils.generate(memberWeiBiAfterValue.doubleValue() * 10000 + ""));
				memberWeiBiAccount.setUpdateTime(new Date());
				weiBiAccountRepository.update(memberWeiBiAccount);
			}
		}
		// ==========购物者积分结算 end=============
	}

	@Override
	public BigDecimal findTotalPayAmountinTimes(String openId, Date start, Date end) {
		return productOrderRepository.findTotalPayAmountinTimes(openId, start, end);
	}
}
